package com.weirblog.resource.permission;

import java.util.Arrays;
import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

import javax.transaction.Transactional;
import javax.ws.rs.FormParam;
import javax.ws.rs.GET;
import javax.ws.rs.POST;
import javax.ws.rs.Path;
import javax.ws.rs.PathParam;
import javax.ws.rs.Produces;
import javax.ws.rs.QueryParam;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;
import javax.ws.rs.core.Response.Status;

import org.apache.commons.lang3.StringUtils;

import com.weirblog.entity.Users;
import com.weirblog.entity.Video;
import com.weirblog.entity.permission.PermRole;
import com.weirblog.entity.permission.PermRolePermission;
import com.weirblog.vo.DataGrid;
import com.weirblog.vo.JsonVO;

import io.quarkus.hibernate.reactive.panache.Panache;
import io.quarkus.hibernate.reactive.panache.PanacheEntityBase;
import io.quarkus.hibernate.reactive.panache.PanacheQuery;
import io.quarkus.panache.common.Page;
import io.quarkus.panache.common.Sort;
import io.quarkus.panache.common.Sort.Direction;
import io.quarkus.qute.Location;
import io.quarkus.qute.Template;
import io.quarkus.qute.TemplateInstance;
import io.smallrye.mutiny.Uni;
import io.smallrye.mutiny.groups.UniAwait;
import io.vertx.core.json.JsonObject;

@Path("role")
public class RoleResource {

	@Location("admin/roleAdd.html")
	Template roleAdd;

	@GET
	@Path("list")
	public Uni<Object> list(@QueryParam("page") Integer page, @QueryParam("rows") Integer rows) {
//		PanacheQuery<PermRole> pageQuery = PermRole.findAll(Sort.by("id", Direction.Descending)).page(page-1, rows);
//		DataGrid<PermRole> dataGrid = new DataGrid<PermRole>(pageQuery.count(), pageQuery.list());
//		return dataGrid;
		return Panache.withTransaction(() -> {
			PanacheQuery<PermRole> findAll = PermRole.findAll();
			Uni<Long> count = findAll.count();
			Uni<List<PermRole>> list = findAll.page(Page.of(page - 1, rows)).list();
			return Uni.combine().all().unis(count, list).combinedWith((c, l) -> new DataGrid<PermRole>(c, l));
		});
	}

	@GET
	@Path("getAll")
	public Uni<List<PermRole>> getAll() {
		return PermRole.findAll().list();
	}

	@GET
	@Path("{id}")
	public Uni<PermRole> get(@PathParam("id") Integer id) {
		Uni<PermRole> entity = PermRole.findById(id);
		return entity;
	}

	@GET
	@Path("addUI")
	@Produces(MediaType.TEXT_HTML)
	public TemplateInstance roleAdd() {
		return roleAdd.data("role", null);
	}

	@POST
	@Path("add")
	@Transactional
	public Uni<Response> add(PermRole permRole) {
//		System.out.println("--------------------------------:" + permRole.id);
		if (permRole.id == null) {

//			Object indefinitely = permRole.<PermRole>persistAndFlush()
//					.flatMap(role -> {
//				if (StringUtils.isNotBlank(role.menuIds)) {
//					return Uni.combine().all()
//							.unis(Arrays.stream(StringUtils.split(role.menuIds, ","))
//									.map(str -> new PermRolePermission(Integer.valueOf(str), role.id).persistAndFlush())
//									.collect(Collectors.toList()))
//							.combinedWith(t -> Uni.createFrom().item(t));
//				} else {
//					return Uni.createFrom().voidItem();
//				}
//			}).await().indefinitely();
//			
//			return indefinitely == null ? Uni.createFrom().item(Response.ok().status(Status.NOT_FOUND).build())
//					:Uni.createFrom().item(Response.ok(new JsonObject().put("msg", "添加成功").put("success", true)).build());

//					onItem().ifNotNull()
//					.transform(entity -> Response.ok(new JsonObject().put("msg", "添加成功").put("success", true)).build())
//					.onItem().ifNull().continueWith(Response.ok().status(Status.NOT_FOUND)::build);

			return permRole.<PermRole>persistAndFlush().flatMap(role -> {
				if (StringUtils.isNotBlank(role.menuIds)) {
					return Uni.combine().all()
							.unis(Arrays.stream(StringUtils.split(role.menuIds, ","))
									.map(str -> new PermRolePermission(Integer.valueOf(str), role.id).persistAndFlush())
									.collect(Collectors.toList()))
							.combinedWith(t -> Uni.createFrom().item(t));
				} else {
					return Uni.createFrom().voidItem();
				}
			})
					.map(rolePermissions -> {
				System.out.println("--------------------------------------------------ok init----------");
				if (rolePermissions == null) {
					System.out.println("--------------------------------------------------ok null----------");
					return Response.ok().status(Status.NOT_FOUND).build();
				} else {
					System.out.println("--------------------------------------------------ok----------");
					return Response.ok(new JsonObject().put("msg", "修改成功").put("success", true)).build();
				}
			}).onFailure().recoverWithItem(e -> Response.ok().status(Status.NOT_FOUND).build());

		} else {
			return PermRole.<PermRole>findById(permRole.id).onItem().ifNotNull().invoke(role -> {
				role.name = permRole.name;
				role.remark = permRole.remark;
				PermRolePermission.delete("roleId", role.id).subscribeAsCompletionStage().toCompletableFuture();
			}).
//					onItem().transformToUni
					
					flatMap(role -> {
				if (StringUtils.isNotBlank(role.menuIds)) {
					return Uni.combine().all()
							.unis(Arrays.stream(StringUtils.split(role.menuIds, ","))
									.map(str -> new PermRolePermission(Integer.valueOf(str), role.id).persistAndFlush())
									.collect(Collectors.toList()))
							.combinedWith(t -> Uni.createFrom().item(t));
				} else {
					return Uni.createFrom().voidItem();
				}
			}).map(rolePermissions -> {
				if (rolePermissions == null) {
					return Response.ok().status(Status.NOT_FOUND).build();
				} else {
					return Response.ok(new JsonObject().put("msg", "修改成功").put("success", true)).build();
				}
			}).onFailure().recoverWithItem(e -> Response.ok().status(Status.NOT_FOUND).build());
		}
	}

	@GET
	@Path("editUI/{id}")
	@Produces(MediaType.TEXT_HTML)
	public TemplateInstance roleEdit(@PathParam("id") Integer id) {
		Uni<PermRole> permRole = Panache.withTransaction(() -> {
			Uni<PermRole> role = PermRole.findById(id);
			Uni<List<PermRolePermission>> list = PermRolePermission.find("roleId", id).list();
			return Uni.combine().all().unis(role, list).combinedWith((r, l) -> {
				List<Integer> permissionIds = l.stream().map(PermRolePermission::getPermissionId)
						.collect(Collectors.toList());
				r.menuIds = StringUtils.join(permissionIds, ",");
				return r;
			});
		});
//		PermRole role = PermRole.findById(id);
//		List<PermRolePermission> list = PermRolePermission.find("role_id", id).list();
//		List<Integer> permissionIds = list.stream().map(PermRolePermission::getPermissionId).collect(Collectors.toList());
//		role.menuIds = StringUtils.join(permissionIds, ",");
		return roleAdd.data("role", permRole);
	}
}
